package com.xdf.wxbebarrel.model;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JavaType;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.xdf.wxbebarrel.model.templateMessage.MetaData;
import com.xdf.wxbebarrel.service.ReqsLogService;
import com.xdf.wxbebarrel.utils.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 请求微信服务器获取客户二维码或者永久二维码都需要
 * 在请求中加入 access_token ，本类用于生成并返回 access_token
 * 本 access_token 同样是拿开发者相关信息请求微信服务器获得的
 * 本 token 默认有效期是7200 秒，并且每天有限制请求新的次数
 * 所以需要缓存起来，如果没有过期就不要向微信服务器请求新的了
 */
@Service
public class WxAccessToken {
    @Autowired
    private SystemConst systemConst;
    private static final String TEMPLATE_ID_AUDIT = "IRUGdjkPP2p8sOXR-g-xtDsnvGkD_hyt-W083VeNo-I";
    private static final String WX_TOKENURL = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET";
    private static WechatAccessToken at;
    @Autowired
    private ReqsLogService dbLog;

    private static final ObjectMapper mapper = new ObjectMapper();
//    @Autowired
//    private TemplateMsgUtils templateMsgUtils;

    // 先检查缓存的 access_token 如果没有过期就直接返回，相反则重新向微信服务器请求新的 access_token
    public String getAccessToken() {
        if(at==null||at.isExpired()) {
            System.out.println("缓存的 access_token 已经过期，即将开始请求新的 access_token");
            dbLog.insert("","WxAccessToken中开始请求新 token");
            getNewAccessToken();
        }else {
            System.out.println("access_token = " + at.toString() + "，仍然有效，直接拿来使用。");
            dbLog.insert("","WxAccessToken中使用现有有效的token");
        }

        return at.getAccess_token();
    }

    private void getNewAccessToken() {
        String url = WX_TOKENURL.replace("APPID", systemConst.WXMP_APPID).replace("APPSECRET", systemConst.WXMP_APPSECRET);
        String szToken = HttpUtils.sendGet(url);

        System.out.println("通过GET请求获取到的TOKEN字符串是：" + szToken);

        JavaType jvt = mapper.getTypeFactory().constructParametricType(HashMap.class,String.class,String.class);
        Map<String,String> jsonObject = null;
        try {
            jsonObject = mapper.readValue(szToken, jvt);
        } catch (JsonProcessingException e) {
            dbLog.insert("解析微信服务器响应来的accessToken为实体对象时出现异常","WxAccessToken#getNewAccessToken");
            throw new RuntimeException(e);
        }
        String access_token="";
        String expire_in = "";
        try {
            access_token = jsonObject.get("access_token");
            expire_in = jsonObject.get("expires_in");
            dbLog.insert("请求了新token:" + access_token + ",expire_in" + expire_in,"WxAccessToken#getNewAccessToken");
        } catch (Exception e) {
            String errCode = jsonObject.get("errcode");
            StringBuilder sb = new StringBuilder();
            switch (errCode) {
                case "40164":
                    sb.append(jsonObject.get("errmsg"));
                    System.out.println(sb.toString());
                    System.out.println("请将上面IP地址添加到白名单中。");
                    dbLog.insert("请将IP地址"+sb+"添加到白名单中","WxAccessToken#getNewAccessToken#catch");
                    return;
                default:
                    System.out.println("向微信服务器请求新的 access_token 时出现异常！");
                    dbLog.insert("请求新token报错误代码：" + errCode,"WxAccessToken#getNewAccessToken#catch");
                    break;
            }
        }
        at = new WechatAccessToken(access_token, expire_in);
    }
}
